package com.wyzz.hr.bo.impl;

import java.io.PrintStream;
import java.math.BigDecimal;
import java.sql.Date;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import org.apache.commons.lang.StringUtils;
import org.hibernate.FetchMode;
import org.hibernate.criterion.DetachedCriteria;
import org.hibernate.criterion.Order;
import org.hibernate.criterion.ProjectionList;
import org.hibernate.criterion.Projections;
import org.hibernate.criterion.Restrictions;

import com.wyzz.hr.base.Status;
import com.wyzz.hr.bo.IDepartmentBO;
import com.wyzz.hr.bo.IEmpshiftBo;
import com.wyzz.hr.bo.ILeavecalendarBO;
import com.wyzz.hr.bo.IOvertimerequestBo;
import com.wyzz.hr.bo.IOvertimetypeBo;
import com.wyzz.hr.bo.IPositionBo;
import com.wyzz.hr.bo.IStatBO;
import com.wyzz.hr.bo.ISysLogBO;
import com.wyzz.hr.bo.IWorkFlowBO;
import com.wyzz.hr.dao.IOvertimerequestDAO;
import com.wyzz.hr.pojo.Attendshift;
import com.wyzz.hr.pojo.Department;
import com.wyzz.hr.pojo.Employee;
import com.wyzz.hr.pojo.Leavetype;
import com.wyzz.hr.pojo.Overtimerequest;
import com.wyzz.hr.pojo.Overtimetype;
import com.wyzz.hr.pojo.Position;
import com.wyzz.hr.spring.SpringBeanFactory;
import com.wyzz.hr.util.BaseCrit;
import com.wyzz.hr.util.DatabaseSysConfigManager;
import com.wyzz.hr.util.DateUtil;
import com.wyzz.hr.util.Pager;
import com.wyzz.hr.util.StringUtil;
import com.wyzz.hr.vo.ExaminSearchBean;
import com.wyzz.hr.vo.OvertimeFormBean;

public class OvertimerequestBoImpl extends EmpApproverBoImpl implements
		IOvertimerequestBo {

	public OvertimerequestBoImpl() {
	}

	public String orInitTime(OvertimeFormBean of_Bean) throws Exception {
		return "SUCC";
	}

	public String orCheckShifts(Overtimerequest or) throws Exception {
		java.util.Date orShiftDate = or.getOrShiftDate();
		IEmpshiftBo empShiftBo = (IEmpshiftBo) SpringBeanFactory
				.getBean("empshiftBO");
		Attendshift as = empShiftBo.getEmpShiftByDate(orShiftDate, or
				.getOrEmpNo());
		if (as == null)
			return "SUCC";
		String isNightShift = "";
		if (as.getAttsNightShift().intValue() == 1)
			isNightShift = "\u591C\u73ED";
		int isInShift = ExaminDateUtil.isTimeInShift(or.getOrStartDate(),
				orShiftDate, as.getAttsSession());
		if (isInShift == 1 || isInShift == 2)
			return (new StringBuilder()).append(
					"\u5F00\u59CB\u65F6\u95F4\u4E0E\u60A8\u7684").append(
					isNightShift).append("\u73ED\u6B21 ").append(
					as.getAttsSession()).append(" \u6709\u51B2\u7A81\uFF01")
					.toString();
		isInShift = ExaminDateUtil.isTimeInShift(or.getOrEndDate(),
				orShiftDate, as.getAttsSession());
		if (isInShift == 2 || isInShift == 3)
			return (new StringBuilder()).append(
					"\u52A0\u73ED\u65F6\u95F4\u4E0E\u60A8\u7684").append(
					isNightShift).append("\u73ED\u6B21 ").append(
					as.getAttsSession()).append(" \u6709\u51B2\u7A81\uFF01")
					.toString();
		int timeInShift = ExaminDateUtil.minutesInShift(or.getOrStartDate(), or
				.getOrEndDate(), orShiftDate, as.getAttsSession());
		if (timeInShift > 0)
			return (new StringBuilder()).append(
					"\u52A0\u73ED\u65F6\u95F4\u4E0E\u60A8\u7684").append(
					isNightShift).append("\u73ED\u6B21 ").append(
					as.getAttsSession()).append(" \u6709\u51B2\u7A81\uFF01")
					.toString();
		else
			return "SUCC";
	}

	public String orCheckTime(Overtimerequest or) {
		String msgConflict = "\u4E0E\u7F16\u53F7\u4E3A{0}\u7684\u52A0\u73ED\u5355\u5B58\u5728\u65F6\u95F4\u51B2\u7A81\uFF01";
		DetachedCriteria dc = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		dc
				.add(Restrictions.eq(Overtimerequest.PROP_OR_EMP_NO, or
						.getOrEmpNo()));
		dc.add(Restrictions.in(Overtimerequest.PROP_OR_STATUS,
				Status.PROCESS_VALID));
		java.util.Date startTime = or.getOrStartDate();
		java.util.Date endTime = or.getOrEndDate();
		dc.add(Restrictions.lt(Overtimerequest.PROP_OR_START_DATE, endTime));
		dc.add(Restrictions.gt(Overtimerequest.PROP_OR_END_DATE, startTime));
		List resultList = or_DAO.findByCriteria(dc);
		if (resultList == null || resultList.size() == 0)
			return "SUCC";
		if (resultList.size() == 1
				&& ((Overtimerequest) resultList.get(0)).getOrId().equals(
						or.getOrId()))
			return "SUCC";
		else
			return StringUtil.message(msgConflict,
					new Object[] { ((Overtimerequest) resultList.get(0))
							.getOrNo() });
	}

	public double getTotalTime(Overtimerequest or, java.util.Date startDate,
			java.util.Date endDate, Integer statusSet[]) {
		DetachedCriteria detachedCriteria = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		java.util.Date startD = DateUtil.convDateTimeToDate(startDate);
		java.util.Date endD = DateUtil.convDateTimeToDate(DateUtil.dateAdd(
				endDate, 1));
		detachedCriteria.add(Restrictions.between(
				Overtimerequest.PROP_OR_START_DATE, startD, endD));
		detachedCriteria.add(Restrictions.eq(Overtimerequest.PROP_OR_OT_NO, or
				.getOrOtNo()));
		detachedCriteria.add(Restrictions.eq(Overtimerequest.PROP_OR_EMP_NO, or
				.getOrEmpNo()));
		detachedCriteria.add(Restrictions.in(Overtimerequest.PROP_OR_STATUS,
				statusSet));
		detachedCriteria.setProjection(Projections.projectionList().add(
				Projections.sum(Overtimerequest.PROP_OR_TOTAL_HOURS)));
		List orList = or_DAO.findByCriteria(detachedCriteria);
		if (orList == null || orList.size() == 0 || orList.get(0) == null) {
			return 0.0D;
		} else {
			BigDecimal total = (BigDecimal) orList.get(0);
			return total.doubleValue();
		}
	}

	public double getTotalTimeRecal(Overtimerequest or,
			java.util.Date startDate, java.util.Date endDate,
			Integer statusSet[]) {
		DetachedCriteria detachedCriteria = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		java.util.Date startD = DateUtil.convDateTimeToDate(startDate);
		java.util.Date endD = DateUtil.convDateTimeToDate(DateUtil.dateAdd(
				endDate, 1));
		detachedCriteria.add(Restrictions.between(
				Overtimerequest.PROP_OR_START_DATE, startD, endD));
		detachedCriteria.add(Restrictions.eq(Overtimerequest.PROP_OR_OT_NO, or
				.getOrOtNo()));
		detachedCriteria.add(Restrictions.eq(Overtimerequest.PROP_OR_EMP_NO, or
				.getOrEmpNo()));
		detachedCriteria.add(Restrictions.in(Overtimerequest.PROP_OR_STATUS,
				statusSet));
		List orList = or_DAO.findByCriteria(detachedCriteria);
		if (orList == null || orList.size() == 0)
			return 0.0D;
		double totalTime = 0.0D;
		boolean recalOr = false;
		for (Iterator i$ = orList.iterator(); i$.hasNext();) {
			Overtimerequest orTemp = (Overtimerequest) i$.next();
			if (orTemp.getOrId().equals(or.getOrId())) {
				recalOr = true;
				totalTime += or.getOrTotalHours().doubleValue();
			} else {
				totalTime += orTemp.getOrTotalHours().doubleValue();
			}
		}

		if (recalOr)
			return totalTime;
		else
			return totalTime + or.getOrTotalHours().doubleValue();
	}

	public double getTotalOTTiaoxiuTime(Overtimerequest ot,
			java.util.Date startDate, java.util.Date endDate, int statusSet[]) {
		DetachedCriteria detachedCriteria = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		detachedCriteria.add(Restrictions.ge(
				Overtimerequest.PROP_OR_START_DATE, startDate));
		detachedCriteria.add(Restrictions.le(Overtimerequest.PROP_OR_END_DATE,
				endDate));
		detachedCriteria.add(Restrictions.eq(Overtimerequest.PROP_OR_EMP_NO, ot
				.getOrEmpNo()));
		if (ot.getOrOtNo() != null)
			detachedCriteria.add(Restrictions.eq(Overtimerequest.PROP_OR_OT_NO,
					ot.getOrOtNo()));
		Integer status[] = new Integer[statusSet.length];
		for (int i = 0; i < status.length; i++)
			status[i] = new Integer(statusSet[i]);

		detachedCriteria.add(Restrictions.in(Overtimerequest.PROP_OR_STATUS,
				status));
		if (ot.getOrId() != null && !ot.getOrId().equals(""))
			detachedCriteria.add(Restrictions.ne(Overtimerequest.PROP_OR_ID, ot
					.getOrId()));
		detachedCriteria.setProjection(Projections.projectionList().add(
				Projections.sum(Overtimerequest.PROP_OR_TIAOXIU_HOURS)));
		List list = or_DAO.findByCriteria(detachedCriteria);
		if (list != null && list.size() > 0) {
			BigDecimal b = (BigDecimal) list.get(0);
			if (b != null)
				return b.doubleValue();
		}
		return 0.0D;
	}

	public List getEmpAllTiaoxiuOrList(Employee currEmp, int statusSet[],
			java.util.Date date, Integer tiaoxiuMatch) {
		String hql = "from Overtimerequest ";
		hql = (new StringBuilder()).append(hql).append("where orEmpNo.id = '")
				.append(currEmp.getId()).append("' and orStatus in(")
				.toString();
		for (int i = 0; i < statusSet.length; i++) {
			hql = (new StringBuilder()).append(hql).append(statusSet[i])
					.toString();
			if (i != statusSet.length - 1)
				hql = (new StringBuilder()).append(hql).append(",").toString();
		}

		hql = (new StringBuilder()).append(hql).append(
				") and orTiaoxiuHoursRemain >= 0.0 ").toString();
		hql = (new StringBuilder()).append(hql).append(
				" and (orTiaoxiuExpire is null or orTiaoxiuExpire >= '")
				.append(new Date(date.getTime())).append("')").toString();
		if (tiaoxiuMatch.intValue() == 0)
			hql = (new StringBuilder()).append(hql).append(
					" order by orShiftDate asc").toString();
		else if (tiaoxiuMatch.intValue() == 1)
			hql = (new StringBuilder()).append(hql).append(
					" order by orOtNo.otNo desc,orShiftDate asc").toString();
		else
			hql = (new StringBuilder())
					.append(hql)
					.append(
							" order by year(orShiftDate) asc,month(orShiftDate) asc,or_ot_no desc,day(orShiftDate) asc")
					.toString();
		List orList = or_DAO.exeHqlList(hql);
		return orList;
	}

	public List getEmpTiaoxiuOrList(Employee currEmp, int statusSet[]) {
		DetachedCriteria detachedCriteria = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		detachedCriteria.createAlias(Overtimerequest.PROP_OR_EMP_NO, "orEmpNo",
				1);
		detachedCriteria
				.createAlias(Overtimerequest.PROP_OR_OT_NO, "orOtNo", 1);
		if (currEmp != null)
			detachedCriteria.add(Restrictions.eq(
					Overtimerequest.PROP_OR_EMP_NO, currEmp));
		Integer status[] = new Integer[statusSet.length];
		for (int i = 0; i < status.length; i++)
			status[i] = new Integer(statusSet[i]);

		detachedCriteria.add(Restrictions.in(Overtimerequest.PROP_OR_STATUS,
				status));
		detachedCriteria.add(Restrictions.ge(
				Overtimerequest.PROP_OR_TIAOXIE_HOURS_REMAIN, new BigDecimal(
						0.0D)));
		detachedCriteria
				.addOrder(Order.asc(Overtimerequest.PROP_OR_START_DATE));
		List orList = or_DAO.findByCriteria(detachedCriteria);
		return orList;
	}

	/**
	 * @deprecated Method searchByOrId is deprecated
	 */

	public Overtimerequest searchByOrId(String orId) {
		String fetch[] = { Overtimerequest.PROP_OR_OT_NO,
				Overtimerequest.PROP_OR_EMP_NO,
				Overtimerequest.PROP_OR_EMP_DEPT,
				Overtimerequest.PROP_OR_CREATE_BY,
				Overtimerequest.PROP_OR_LAST_CHANGE_BY };
		Object results = or_DAO.loadObject(
				com.wyzz.hr.pojo.Overtimerequest.class, orId, fetch,
				new boolean[0]);
		if (results == null) {
			return null;
		} else {
			Overtimerequest result = (Overtimerequest) results;
			return result;
		}
	}

	/**
	 * @deprecated Method deleteOvertimereuqest is deprecated
	 */

	public List deleteOvertimereuqest(String orId, Employee currentEmployee) {
		List errors = new ArrayList();
		try {
			Overtimerequest or = searchByOrId(orId);
			if (or == null) {
				throw new Exception(
						"\u64CD\u4F5C\u4E0D\u6210\u529F\uFF0C\u8BF7\u91CD\u8BD5\uFF01");
			} else {
				ISysLogBO logBO = (ISysLogBO) SpringBeanFactory
						.getBean("logBO");
				logBO.deleteLogs("overtimerequest", (new StringBuilder())
						.append(orId).append("").toString());
				or_DAO.deleteObject(or);
				return errors;
			}
		} catch (Exception e) {
			e.printStackTrace();
			errors.add(e.getMessage());
			return errors;
		}
	}

	public String checkMonthLimit(Overtimerequest or) {
		String msgConflict = "{0}\u5F53\u6708\u52A0\u73ED\u6700\u591A\u4E3A{1}\u5C0F\u65F6\uFF0C\u60A8\u7684\u7533\u8BF7\u5DF2\u8D85\u8FC7\u4E0A\u9650\uFF01";
		Overtimetype overtimetype = ot_BO.searchByID(or.getOrOtNo().getOtNo());
		if (overtimetype.getOtOverLimit() == null)
			return "SUCC";
		double limitTime = overtimetype.getOtOverLimit().intValue();
		String config = DatabaseSysConfigManager.getInstance().getProperty(
				"sys.examin.month.sum");
		java.util.Date dateArr[] = ExaminDateUtil.getDateArray(or
				.getOrStartDate(), config);
		double actualTime = getTotalTimeRecal(or, dateArr[0], dateArr[1],
				Status.PROCESS_VALID);
		if (actualTime <= limitTime)
			return "SUCC";
		else
			return StringUtil.message(msgConflict, new Object[] {
					or.getOrOtNo().getOtName(), Double.valueOf(limitTime) });
	}

	public double getMonthTotal(Overtimerequest or, Integer status[]) {
		String config = DatabaseSysConfigManager.getInstance().getProperty(
				"sys.examin.month.sum");
		java.util.Date dateArr[] = ExaminDateUtil.getDateArray(or
				.getOrStartDate(), config);
		double usedTime = getTotalTime(or, dateArr[0], dateArr[1], status);
		return usedTime;
	}

	public List loadOvertimeRequests(String orIDs[], String fetch[]) {
		List result;
		try {
			DetachedCriteria dc = DetachedCriteria
					.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
			for (int i = 0; i < fetch.length; i++)
				dc.setFetchMode(fetch[i], FetchMode.JOIN);

			BaseCrit.addDC(dc, Overtimerequest.PROP_OR_ID, "in", orIDs);
			dc.addOrder(Order.asc(Overtimerequest.PROP_OR_NO));
			result = or_DAO.findByCriteria(dc);
			if (result.size() == 0)
				return null;
		} catch (Exception e) {
			return null;
		}
		return result;
	}

	public Overtimerequest loadOvertimerequest(String orID) {
		String fetch[] = {
				Overtimerequest.PROP_OR_EMP_NO,
				(new StringBuilder()).append(Overtimerequest.PROP_OR_EMP_NO)
						.append(".").append(Employee.PROP_EMP_LOCATION_NO)
						.toString(),
				(new StringBuilder()).append(Overtimerequest.PROP_OR_EMP_NO)
						.append(".").append(Employee.PROP_EMP_DEPT_NO)
						.toString(),
				Overtimerequest.PROP_OR_CREATE_BY,
				(new StringBuilder()).append(Overtimerequest.PROP_OR_CREATE_BY)
						.append(".").append(Employee.PROP_EMP_LOCATION_NO)
						.toString(),
				(new StringBuilder()).append(Overtimerequest.PROP_OR_CREATE_BY)
						.append(".").append(Employee.PROP_EMP_DEPT_NO)
						.toString(),
				Overtimerequest.PROP_OR_LAST_CHANGE_BY,
				(new StringBuilder()).append(
						Overtimerequest.PROP_OR_LAST_CHANGE_BY).append(".")
						.append(Employee.PROP_EMP_LOCATION_NO).toString(),
				(new StringBuilder()).append(
						Overtimerequest.PROP_OR_LAST_CHANGE_BY).append(".")
						.append(Employee.PROP_EMP_DEPT_NO).toString(),
				Overtimerequest.PROP_OR_EMP_DEPT, Overtimerequest.PROP_OR_OT_NO };
		Overtimerequest resultOR = (Overtimerequest) or_DAO.loadObject(
				com.wyzz.hr.pojo.Overtimerequest.class, orID, fetch,
				new boolean[0]);
		return resultOR;
	}

	public Overtimerequest loadOvertimerequest(String orID, String fetch[]) {
		Overtimerequest resultOR = (Overtimerequest) or_DAO.loadObject(
				com.wyzz.hr.pojo.Overtimerequest.class, orID, fetch,
				new boolean[0]);
		return resultOR;
	}

	public void examinSearch(ExaminSearchBean searchBean, DetachedCriteria dc,
			Pager page) {
		dc.setFetchMode(Overtimerequest.PROP_OR_CREATE_BY, FetchMode.JOIN);
		dc.setFetchMode(Overtimerequest.PROP_OR_LAST_CHANGE_BY, FetchMode.JOIN);
		dc.createAlias(Overtimerequest.PROP_OR_EMP_NO, "emp", 1);
		dc.createAlias(Overtimerequest.PROP_OR_CREATE_BY, "creator");
		dc.createAlias(Overtimerequest.PROP_OR_EMP_DEPT, "dept");
		dc.createAlias((new StringBuilder()).append("emp.").append(
				Employee.PROP_EMP_PB_NO).toString(), "empOrgPB", 1);
		dc.createAlias(Overtimerequest.PROP_OR_OT_NO, "orOtNo", 1);
		dc.createAlias((new StringBuilder()).append("emp.").append(
				Employee.PROP_EMP_DEPT_NO).toString(), "empOrgDept", 1);
		dc.createAlias((new StringBuilder()).append("emp.").append(
				Employee.PROP_EMP_LOCATION_NO).toString(), "empOrgLoc", 1);
		try {
			if (!StringUtils.isEmpty(searchBean.getNo()))
				BaseCrit.addDC(dc, Overtimerequest.PROP_OR_NO, "eq",
						new Integer[] { Integer.valueOf(Integer
								.parseInt(searchBean.getNo())) });
		} catch (Exception ex) {
			System.out.println((new StringBuilder()).append(
					"==========error: cannot calc No").append(
					searchBean.getNo()).toString());
		}
		BaseCrit.addDC(dc, Overtimerequest.PROP_OR_REASON, "like",
				new String[] { searchBean.getReason() });
		String alias[] = { Overtimerequest.PROP_OR_START_DATE,
				Overtimerequest.PROP_OR_END_DATE };
		BaseCrit.addDCTwoDateRange(dc, alias, searchBean.getStartDate(),
				searchBean.getEndDate());
		if (!StringUtils.isEmpty(searchBean.getTypeNo()))
			BaseCrit.addDC(dc, Overtimerequest.PROP_OR_OT_NO,
					Overtimetype.PROP_OT_NO, new Object[] { new Overtimetype(
							searchBean.getTypeNo()) });
		BaseCrit.addDC(dc, Overtimerequest.PROP_OR_STATUS, "eq",
				new Integer[] { searchBean.getStatu() });
		BaseCrit.addEmpDC(dc, "emp", searchBean.getEmp());
		BaseCrit.addDeptDC(dc, (new StringBuilder()).append("emp.").append(
				Employee.PROP_EMP_DEPT_NO).toString(), (new StringBuilder())
				.append("emp.").append(Employee.PROP_EMP_PB_NO).toString(),
				Integer.valueOf(1), new Department(searchBean.getDepNo()));
		page.splitPage(dc);
		setOrder(dc, page.getOrder());
		List result = or_DAO.findByCriteria(dc, page.getPageSize(), page
				.getCurrentPage());
		searchBean.setResult(result);
	}

	public void approverMgrSearch(ExaminSearchBean searchBean,
			Employee currentEmp, Pager page) {
		DetachedCriteria dc = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		IPositionBo posBo = (IPositionBo) SpringBeanFactory
				.getBean("positionBo");
		Position pos = posBo.getPosByEmpNo(currentEmp.getId(), new String[0]);
		BaseCrit.addDC(dc, Overtimerequest.PROP_OR_NEXT_APPROVER, "eq",
				new String[] { pos.getId() });
		BaseCrit.addDC(dc, Overtimerequest.PROP_OR_STATUS, "in",
				Status.IN_MGR_PROCESS);
		examinSearch(searchBean, dc, page);
	}

	public void approverHRSearch(ExaminSearchBean searchBean, Pager page) {
		DetachedCriteria dc = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		dc.add(Restrictions.isNull(Overtimerequest.PROP_OR_NEXT_APPROVER));
		dc.add(Restrictions.isNull(Overtimerequest.PROP_OR_NEXT_APPROVER));
		dc.add(Restrictions.in(Overtimerequest.PROP_OR_STATUS,
				Status.IN_PROCESS));
		examinSearch(searchBean, dc, page);
	}

	public void ExaminOwnSearch(ExaminSearchBean searchBean, Pager page,
			String empNo) {
		DetachedCriteria dc = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		dc.add(Restrictions.eq("orEmpNo.id", empNo));
		examinSearch(searchBean, dc, page);
	}

	public void orAllSearch(ExaminSearchBean searchBean, Pager page) {
		DetachedCriteria dc = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		examinSearch(searchBean, dc, page);
	}

	private void setOrder(DetachedCriteria detachedCriteria, String order) {
		if (order != null && order.trim().length() > 1
				&& order.indexOf("-") > -1) {
			String ordeName = null;
			String operate = null;
			String params[] = order.split("-");
			if (params.length > 0)
				ordeName = params[0];
			if (params.length > 1)
				operate = params[1];
			if (ordeName.equals("id"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order
							.asc(Overtimerequest.PROP_OR_NO));
				else
					detachedCriteria.addOrder(Order
							.desc(Overtimerequest.PROP_OR_NO));
			if (ordeName.equals("dep"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order
							.asc((new StringBuilder()).append("empOrgDept.")
									.append(Department.PROP_DEPARTMENT_NAME)
									.toString()));
				else
					detachedCriteria.addOrder(Order
							.desc((new StringBuilder()).append("empOrgDept.")
									.append(Department.PROP_DEPARTMENT_NAME)
									.toString()));
			if (ordeName.equals("emp"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order.asc((new StringBuilder())
							.append("emp.").append(Employee.PROP_EMP_NAME)
							.toString()));
				else
					detachedCriteria.addOrder(Order.desc((new StringBuilder())
							.append("emp.").append(Employee.PROP_EMP_NAME)
							.toString()));
			if (ordeName.equals("type"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order.asc((new StringBuilder())
							.append(Overtimerequest.PROP_OR_OT_NO).append(".")
							.append(Overtimetype.PROP_OT_NAME).toString()));
				else
					detachedCriteria.addOrder(Order.desc((new StringBuilder())
							.append(Overtimerequest.PROP_OR_OT_NO).append(".")
							.append(Overtimetype.PROP_OT_NAME).toString()));
			if (ordeName.equals("reason"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order
							.asc(Overtimerequest.PROP_OR_REASON));
				else
					detachedCriteria.addOrder(Order
							.desc(Overtimerequest.PROP_OR_REASON));
			if (ordeName.equals("startT"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order
							.asc(Overtimerequest.PROP_OR_START_DATE));
				else
					detachedCriteria.addOrder(Order
							.desc(Overtimerequest.PROP_OR_START_DATE));
			if (ordeName.equals("total"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order
							.asc(Overtimerequest.PROP_OR_TOTAL_HOURS));
				else
					detachedCriteria.addOrder(Order
							.desc(Overtimerequest.PROP_OR_TOTAL_HOURS));
			if (ordeName.equals("statu"))
				if (operate.equals("up"))
					detachedCriteria.addOrder(Order
							.asc(Overtimerequest.PROP_OR_STATUS));
				else
					detachedCriteria.addOrder(Order
							.desc(Overtimerequest.PROP_OR_STATUS));
		} else {
			detachedCriteria.addOrder(Order.desc(Overtimerequest.PROP_OR_NO));
		}
	}

	public String[][] getOvertimeTotal(String empId) {
		Calendar calendar = Calendar.getInstance();
		String hql = (new StringBuilder())
				.append(
						"select orOtNo.otName,sum(orTotalHours) from Overtimerequest where orStatus in (2,5,14,15,16) and orEmpNo.id='")
				.append(empId).append("' and YEAR(orStartDate)=").append(
						calendar.get(1)).append(" group by orOtNo.otName")
				.append(" order by orOtNo.otName").toString();
		List list = or_DAO.exeHqlList(hql);
		if (list == null || list.size() == 0)
			return (String[][]) null;
		hql = "select otName FROM Overtimetype ";
		List otType = or_DAO.exeHqlList(hql);
		Object objectTemp[] = null;
		List tempNewAdd = new ArrayList();
		for (int i = 0; i < otType.size(); i++) {
			objectTemp = new Object[2];
			Boolean flag = Boolean.valueOf(false);
			int j = 0;
			do {
				if (j >= list.size())
					break;
				Object objectArray[] = (Object[]) (Object[]) list.get(j);
				if (otType.get(i).equals(objectArray[0])) {
					flag = Boolean.valueOf(true);
					break;
				}
				j++;
			} while (true);
			if (!flag.booleanValue()) {
				objectTemp[0] = otType.get(i);
				objectTemp[1] = "0.0";
				tempNewAdd.add(((Object) (objectTemp)));
			}
		}

		if (tempNewAdd.size() > 0)
			list.addAll(tempNewAdd);
		hql = (new StringBuilder())
				.append(
						"select orOtNo.otName,sum(orTotalHours) from Overtimerequest where orStatus in (2,5,14) and orEmpNo.id='")
				.append(empId).append("' and YEAR(orStartDate)=").append(
						calendar.get(1)).append(" group by orOtNo.otName")
				.append(" order by orOtNo.otName").toString();
		List toApproveList = or_DAO.exeHqlList(hql);
		String result[][] = new String[14][list.size() + 1];
		for (int i = 0; i < result.length; i++) {
			for (int j = 0; j < result[i].length; j++)
				result[i][j] = "0.0";

		}

		int toApproveIndex = 0;
		for (int i = 0; i < list.size(); i++) {
			result[13][i] = ((Object[]) (Object[]) list.get(i))[0].toString();
			result[12][i] = ((Object[]) (Object[]) list.get(i))[1].toString();
			if (toApproveList.size() > 0
					&& toApproveIndex < toApproveList.size()
					&& result[13][i]
							.equals(((Object[]) (Object[]) toApproveList
									.get(toApproveIndex))[0].toString())) {
				double toApproveSum = Double
						.parseDouble(((Object[]) (Object[]) toApproveList
								.get(toApproveIndex))[1].toString());
				result[12][i] = (new StringBuilder()).append(result[12][i])
						.append("(").append(toApproveSum).append(
								"\u5C0F\u65F6\u5F85\u5BA1)").toString();
				toApproveIndex++;
			}
		}

		hql = (new StringBuilder())
				.append(
						"select MONTH(orStartDate),orOtNo.otName,sum(orTotalHours) from Overtimerequest where orStatus in (2,5,14,15,16) and orEmpNo.id='")
				.append(empId).append("' and YEAR(orStartDate)=").append(
						calendar.get(1)).append(
						" group by MONTH(orStartDate),orOtNo.otName").append(
						" order by MONTH(orStartDate),orOtNo.otName")
				.toString();
		List totalList = or_DAO.exeHqlList(hql);
		hql = (new StringBuilder())
				.append(
						"select MONTH(orStartDate),orOtNo.otName,sum(orTotalHours)  from Overtimerequest where orStatus in (2,5,14) and orEmpNo.id='")
				.append(empId).append("' and YEAR(orStartDate)=").append(
						calendar.get(1)).append(
						" group by MONTH(orStartDate),orOtNo.otName").append(
						" order by MONTH(orStartDate),orOtNo.otName")
				.toString();
		List totalToApproveList = or_DAO.exeHqlList(hql);
		int index = 0;
		toApproveIndex = 0;
		int currentMonth = 1;
		double monthTotal = 0.0D;
		double totalOvertime = 0.0D;
		double monthToAppTotal = 0.0D;
		double totalToAppOvertime = 0.0D;
		int i = 0;
		do {
			if (i >= totalList.size())
				break;
			Object item[] = (Object[]) (Object[]) totalList.get(i);
			int month = Integer.parseInt(item[0].toString());
			if (month == currentMonth) {
				if (((Object[]) (Object[]) list.get(index))[0].toString()
						.equals(item[1].toString())) {
					result[currentMonth - 1][index] = item[2].toString();
					monthTotal += Double.parseDouble(item[2].toString());
					i++;
					if (totalToApproveList != null
							&& toApproveIndex < totalToApproveList.size()
							&& ((Object[]) (Object[]) totalToApproveList
									.get(toApproveIndex))[0].toString().equals(
									item[0].toString())
							&& ((Object[]) (Object[]) totalToApproveList
									.get(toApproveIndex))[1].toString().equals(
									item[1].toString())) {
						double toApprove = Double
								.parseDouble(((Object[]) (Object[]) totalToApproveList
										.get(toApproveIndex))[2].toString());
						monthToAppTotal += toApprove;
						result[currentMonth - 1][index] = (new StringBuilder())
								.append(result[currentMonth - 1][index])
								.append("(").append(toApprove).append(
										"\u5C0F\u65F6\u5F85\u5BA1)").toString();
						toApproveIndex++;
					}
				} else {
					index++;
				}
			} else {
				String monthToAppTotalTmp = monthToAppTotal <= 0.0D ? ""
						: (new StringBuilder()).append("(").append(
								monthToAppTotal).append(
								"\u5C0F\u65F6\u5F85\u5BA1)").toString();
				result[currentMonth - 1][list.size()] = (new StringBuilder())
						.append(monthTotal).append(monthToAppTotalTmp)
						.toString();
				totalOvertime += monthTotal;
				totalToAppOvertime += monthToAppTotal;
				monthTotal = 0.0D;
				monthToAppTotal = 0.0D;
				currentMonth = month;
				index = 0;
			}
		} while (true);
		String monthToAppTotalTmp = monthToAppTotal <= 0.0D ? ""
				: (new StringBuilder()).append("(").append(monthToAppTotal)
						.append("\u5C0F\u65F6\u5F85\u5BA1)").toString();
		result[currentMonth - 1][list.size()] = (new StringBuilder()).append(
				monthTotal).append(monthToAppTotalTmp).toString();
		totalOvertime += monthTotal;
		totalToAppOvertime += monthToAppTotal;
		result[13][list.size()] = "\u6708\u5EA6\u6C47\u603B";
		String totalToAppTotalTmp = totalToAppOvertime <= 0.0D ? ""
				: (new StringBuilder()).append("(").append(totalToAppOvertime)
						.append("\u5C0F\u65F6\u5F85\u5BA1)").toString();
		result[12][list.size()] = (new StringBuilder()).append(totalOvertime)
				.append(totalToAppTotalTmp).toString();
		return result;
	}

	public void deleteExtraOvertimerequest() {
		String deleteHql = "delete from Overtimerequest where orNextApprover is not null and orNextApprover!=''";
		or_DAO.exeHql(deleteHql);
	}

	public double[] countHoursAndRemainHours(String empId, java.util.Date date) {
		double result[] = { 0.0D, 0.0D };
		StringBuffer hql = new StringBuffer(
				(new StringBuilder())
						.append(
								"select sum(orTiaoxiuHours),sum(orTiaoxiuHoursRemain) from Overtimerequest where orEmpNo.id = '")
						.append(empId).append("'").toString());
		hql.append(" and orStatus in (").append(15).append(",").append(16)
				.append(")");
		hql.append(" and (orTiaoxiuExpire is null or orTiaoxiuExpire >= '")
				.append(new Date(date.getTime())).append("')");
		List list = or_DAO.exeHqlList(hql.toString());
		if (list == null) {
			return result;
		} else {
			Object obj[] = (Object[]) (Object[]) list.get(0);
			result[0] = Double.parseDouble(obj[0].toString());
			result[1] = Double.parseDouble(obj[1].toString());
			return result;
		}
	}

	public Map provideOvertimeRequestData(java.util.Date startDate,
			java.util.Date endDate, List emps) {
		Integer status[] = { Integer.valueOf(15), Integer.valueOf(16) };
		IOvertimerequestDAO dao = (IOvertimerequestDAO) SpringBeanFactory
				.getBean("overtimerequestDAO");
		DetachedCriteria dc = DetachedCriteria
				.forClass(com.wyzz.hr.pojo.Overtimerequest.class);
		dc.createAlias(Overtimerequest.PROP_OR_OT_NO, "orOtNo", 1);
		if (emps.size() > 0 && emps.size() <= 500)
			dc.add(Restrictions.in("orEmpNo", emps));
		dc.add(Restrictions.in(Overtimerequest.PROP_OR_STATUS, status));
		dc.add(Restrictions.and(Restrictions.ge(
				Overtimerequest.PROP_OR_SHIFT_DATE, startDate), Restrictions
				.le(Overtimerequest.PROP_OR_SHIFT_DATE, endDate)));
		dc.addOrder(Order.asc(Overtimerequest.PROP_OR_START_DATE_APPLY));
		List orList = dao.findByCriteria(dc);
		Map empOrMap = new HashMap();
		List tempOrList = null;
		Overtimerequest or;
		for (Iterator i$ = orList.iterator(); i$.hasNext(); tempOrList.add(or)) {
			or = (Overtimerequest) i$.next();
			String key = (new StringBuilder()).append(or.getOrEmpNo().getId())
					.append(DateUtil.formatDate(or.getOrShiftDate()))
					.toString();
			tempOrList = (List) empOrMap.get(key);
			if (tempOrList == null) {
				tempOrList = new ArrayList();
				empOrMap.put(key, tempOrList);
			}
		}

		return empOrMap;
	}

	public String[][] getEmpTiaoxiu(Leavetype lt, java.util.Date now,
			List tiaoxiuOrList) {
		Calendar cal = Calendar.getInstance();
		int arrayLength = 0;
		int sum = 0;
		boolean flag = false;
		if (lt != null) {
			String ltOtherParameter = lt.getLtOtherParameter();
			sum = Integer.parseInt(ltOtherParameter.substring(0,
					ltOtherParameter.length() - 1));
			flag = true;
			arrayLength = sum;
			if (ltOtherParameter.indexOf("d") != -1) {
				flag = false;
				arrayLength = 1;
			}
		}
		String result[][] = new String[arrayLength + 1][4];
		double common_usedTime = 0.0D;
		double common_wastedTime = 0.0D;
		double common_sumTime = 0.0D;
		double weekEnd_usedTime = 0.0D;
		double weekEnd_wastedTime = 0.0D;
		double weekEnd_sumTime = 0.0D;
		double holiday_usedTime = 0.0D;
		double holiday_wastedTime = 0.0D;
		double holiday_sumTime = 0.0D;
		if (flag) {
			String config = DatabaseSysConfigManager.getInstance().getProperty(
					"sys.examin.month.sum");
			for (int i = 1; i <= sum; i++) {
				java.util.Date thisDate = DateUtil.dateTimeAdd(now, i - sum, 2);
				java.util.Date dateArr[] = ExaminDateUtil.getDateArray(
						thisDate, config);
				Iterator i$ = tiaoxiuOrList.iterator();
				do {
					if (!i$.hasNext())
						break;
					Overtimerequest ot = (Overtimerequest) i$.next();
					if (!ot.getOrShiftDate().before(dateArr[0])
							&& !ot.getOrShiftDate().after(dateArr[1]))
						if (ot.getOrOtNo().getOtNo().equals("03")) {
							holiday_sumTime += ot.getOrTiaoxiuHours()
									.doubleValue();
							holiday_usedTime += ot.getOrTiaoxiuHours()
									.doubleValue()
									- ot.getOrTiaoxiuHoursRemain()
											.doubleValue();
							if (ot.getOrTiaoxiuExpire() != null
									&& dateArr[1]
											.after(ot.getOrTiaoxiuExpire()))
								holiday_wastedTime += ot
										.getOrTiaoxiuHoursRemain()
										.doubleValue();
						} else if (ot.getOrOtNo().getOtNo().equals("02")) {
							weekEnd_sumTime += ot.getOrTiaoxiuHours()
									.doubleValue();
							weekEnd_usedTime += ot.getOrTiaoxiuHours()
									.doubleValue()
									- ot.getOrTiaoxiuHoursRemain()
											.doubleValue();
							if (ot.getOrTiaoxiuExpire() != null
									&& dateArr[1]
											.after(ot.getOrTiaoxiuExpire()))
								weekEnd_wastedTime += ot
										.getOrTiaoxiuHoursRemain()
										.doubleValue();
						} else {
							common_sumTime += ot.getOrTiaoxiuHours()
									.doubleValue();
							common_usedTime += ot.getOrTiaoxiuHours()
									.doubleValue()
									- ot.getOrTiaoxiuHoursRemain()
											.doubleValue();
							if (ot.getOrTiaoxiuExpire() != null
									&& dateArr[1]
											.after(ot.getOrTiaoxiuExpire()))
								common_wastedTime += ot
										.getOrTiaoxiuHoursRemain()
										.doubleValue();
						}
				} while (true);
				cal.setTime(thisDate);
				result[i - 1][0] = (new StringBuilder()).append(
						String.valueOf(cal.get(2) + 1)).append("\u6708")
						.toString();
				result[i - 1][1] = (new StringBuilder()).append(
						String.valueOf(common_usedTime)).append("-").append(
						String.valueOf(common_sumTime - common_wastedTime
								- common_usedTime)).toString();
				result[i - 1][2] = (new StringBuilder()).append(
						String.valueOf(weekEnd_usedTime)).append("-").append(
						String.valueOf(weekEnd_sumTime - weekEnd_wastedTime
								- weekEnd_usedTime)).toString();
				result[i - 1][3] = (new StringBuilder()).append(
						String.valueOf(holiday_usedTime)).append("-").append(
						String.valueOf(holiday_sumTime - holiday_wastedTime
								- holiday_usedTime)).toString();
				common_usedTime = 0.0D;
				common_wastedTime = 0.0D;
				common_sumTime = 0.0D;
				weekEnd_usedTime = 0.0D;
				weekEnd_wastedTime = 0.0D;
				weekEnd_sumTime = 0.0D;
				holiday_usedTime = 0.0D;
				holiday_wastedTime = 0.0D;
				holiday_sumTime = 0.0D;
			}

		}
		cal.setTime(now);
		Iterator i$ = tiaoxiuOrList.iterator();
		do {
			if (!i$.hasNext())
				break;
			Overtimerequest ot = (Overtimerequest) i$.next();
			if (ot.getOrOtNo().getOtNo().equals("03")) {
				holiday_sumTime += ot.getOrTiaoxiuHours().doubleValue();
				holiday_usedTime += ot.getOrTiaoxiuHours().doubleValue()
						- ot.getOrTiaoxiuHoursRemain().doubleValue();
				if (ot.getOrTiaoxiuExpire() != null
						&& now.after(ot.getOrTiaoxiuExpire()))
					holiday_wastedTime += ot.getOrTiaoxiuHoursRemain()
							.doubleValue();
			} else if (ot.getOrOtNo().getOtNo().equals("02")) {
				weekEnd_sumTime += ot.getOrTiaoxiuHours().doubleValue();
				weekEnd_usedTime += ot.getOrTiaoxiuHours().doubleValue()
						- ot.getOrTiaoxiuHoursRemain().doubleValue();
				if (ot.getOrTiaoxiuExpire() != null
						&& now.after(ot.getOrTiaoxiuExpire()))
					weekEnd_wastedTime += ot.getOrTiaoxiuHoursRemain()
							.doubleValue();
			} else {
				common_sumTime += ot.getOrTiaoxiuHours().doubleValue();
				common_usedTime += ot.getOrTiaoxiuHours().doubleValue()
						- ot.getOrTiaoxiuHoursRemain().doubleValue();
				if (ot.getOrTiaoxiuExpire() != null
						&& now.after(ot.getOrTiaoxiuExpire()))
					common_wastedTime += ot.getOrTiaoxiuHoursRemain()
							.doubleValue();
			}
		} while (true);
		result[arrayLength][0] = "\u5408\u8BA1";
		result[arrayLength][1] = (new StringBuilder()).append(
				String.valueOf(common_usedTime)).append("-").append(
				String.valueOf(common_sumTime - common_wastedTime
						- common_usedTime)).toString();
		result[arrayLength][2] = (new StringBuilder()).append(
				String.valueOf(weekEnd_usedTime)).append("-").append(
				String.valueOf(weekEnd_sumTime - weekEnd_wastedTime
						- weekEnd_usedTime)).toString();
		result[arrayLength][3] = (new StringBuilder()).append(
				String.valueOf(holiday_usedTime)).append("-").append(
				String.valueOf(holiday_sumTime - holiday_wastedTime
						- holiday_usedTime)).toString();
		return result;
	}

	public IStatBO getSt_BO() {
		return st_BO;
	}

	public void setSt_BO(IStatBO sc_BO) {
		st_BO = sc_BO;
	}

	public IDepartmentBO getDp_BO() {
		return dp_BO;
	}

	public void setDp_BO(IDepartmentBO dp_BO) {
		this.dp_BO = dp_BO;
	}

	public ILeavecalendarBO getLcBO() {
		return lcBO;
	}

	public void setLcBO(ILeavecalendarBO lcBO) {
		this.lcBO = lcBO;
	}

	public IWorkFlowBO getWorkFlowBO() {
		return workFlowBO;
	}

	public void setWorkFlowBO(IWorkFlowBO workFlowBO) {
		this.workFlowBO = workFlowBO;
	}

	public IOvertimetypeBo getOt_BO() {
		return ot_BO;
	}

	public void setOt_BO(IOvertimetypeBo ot_BO) {
		this.ot_BO = ot_BO;
	}

	public IOvertimerequestDAO getOr_DAO() {
		return or_DAO;
	}

	public void setOr_DAO(IOvertimerequestDAO or_DAO) {
		this.or_DAO = or_DAO;
	}

	private IOvertimetypeBo ot_BO;
	private IStatBO st_BO;
	private IDepartmentBO dp_BO;
	private IWorkFlowBO workFlowBO;
	private ILeavecalendarBO lcBO;
	private IOvertimerequestDAO or_DAO;
}
